package persistance.dal;

import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.Calendar;
import ucc.objects.CaisseDuJourDTO;
import ucc.objects.ClasseDeProduitDTO;
import ucc.objects.CompteUtilisateurDTO;
import ucc.objects.ProduitDTO;
import ucc.request.UccViewer;
import biz.BizFactory;

public class CaisseDuJourFinderImpl implements CaisseDuJourFinder {

	private PreparedStatement q1;
	private PreparedStatement q2;
	private PreparedStatement q3;
	private PreparedStatement q4;
	private PreparedStatement q5;
	private PreparedStatement q6;
	private final String Q1 = "select * from caisse.caisses_du_jour where id_caisse_du_jour=?";
	private final String Q2 = "select * from caisse.caisses_du_jour";
	private final String Q3 = "select * from caisse.caisses_du_jour where ouverture>=? and fermeture<=?";
	private final String Q4 = "select * from caisse.caisses_du_jour where utilisateur=? and fermeture is null";
	private final String Q5 = "select sum(prix_total_vente) as montant from caisse.vue_calcul_quantite where id_caisse_du_jour=?";
	private final String Q6 = "select * from caisse.vue_liste_produits_vendus where id_caisse_du_jour=? and id_classe_de_produit=? and vente_animateur=?";

	public CaisseDuJourFinderImpl() {
		this.q1 = DalBackEndServices.INSTANCE.prepare(Q1);
		this.q2 = DalBackEndServices.INSTANCE.prepare(Q2);
		this.q3 = DalBackEndServices.INSTANCE.prepare(Q3);
		this.q4 = DalBackEndServices.INSTANCE.prepare(Q4);
		this.q5 = DalBackEndServices.INSTANCE.prepare(Q5);
		this.q6 = DalBackEndServices.INSTANCE.prepare(Q6);
	}

	public ArrayList<CompteUtilisateurDTO> lesComptesUtilisateurs() {
		ResultSet rs = null;
		ArrayList<CompteUtilisateurDTO> listeCompteUtilisateur = new ArrayList<CompteUtilisateurDTO>();
		try {
			rs = q2.executeQuery();
			while (rs.next()) {
				CompteUtilisateurDTO compteUtilisateur = BizFactory.INSTANCE
						.createEmptyCompteUtilisateurDTO();

				compteUtilisateur.setNomDUtilisateur(rs
						.getString("nom_utilisateur"));
				compteUtilisateur.setMotDePasse(rs.getString("mot_de_passe"));
				compteUtilisateur.setFonction(UccViewer.INSTANCE
						.laFonctionNum(rs.getInt("id_fonction")));
				compteUtilisateur.setNom(rs.getString("nom"));
				compteUtilisateur.setPrenom(rs.getString("prenom"));
				compteUtilisateur.setTelephone(rs.getString("telephone"));

				listeCompteUtilisateur.add(compteUtilisateur);
			}
			return listeCompteUtilisateur;
		} catch (SQLException e) {
			System.out.println("[E][SQL] : ");
			e.printStackTrace();
		}
		return null;
	}

	public CaisseDuJourDTO laCaisseDuJourCompleteNum(int id) {
		ResultSet rs = null;
		try {
			q1.setInt(1, id);
			rs = q1.executeQuery();
			CaisseDuJourDTO caisseDuJour = BizFactory.INSTANCE
					.createEmptyCaisseDuJourDTO();
			while (rs.next()) {
				caisseDuJour.setId(id);
				caisseDuJour.setUtilisateur(UccViewer.INSTANCE
						.leCompteUtilisateurDe(rs.getString("utilisateur")));
				Calendar ouverture = Calendar.getInstance();
				ouverture.setTimeInMillis(rs.getTimestamp("ouverture")
						.getTime());
				caisseDuJour.setOuverture(ouverture);
				caisseDuJour.setFondDeCaisseDeDepart(rs
						.getDouble("fond_de_caisse_depart"));
				Calendar fermeture = Calendar.getInstance();
				if (rs.getTimestamp("fermeture") == null)
					fermeture = null;
				else
					fermeture.setTimeInMillis(rs.getTimestamp("fermeture")
							.getTime());
				caisseDuJour.setFermeture(fermeture);
				caisseDuJour.setFondDeCaisseDeFermeture(rs
						.getDouble("fond_de_caisse_fermeture"));
				caisseDuJour.setRemunerationUtilisateur(rs
						.getDouble("remuneration_utilisateur"));
				caisseDuJour.setOperations(UccViewer.INSTANCE
						.lesOperationsDeLaCaisse(caisseDuJour));
			}
			return caisseDuJour;
		} catch (SQLException e) {
			System.out.println("[E][SQL] : ");
			e.printStackTrace();
		}
		return null;
	}

	public ArrayList<CaisseDuJourDTO> lesCaissesDuJourCompletes() {
		ResultSet rs = null;
		ArrayList<CaisseDuJourDTO> listeCaissesDuJour = new ArrayList<CaisseDuJourDTO>();
		try {
			rs = q2.executeQuery();
			while (rs.next()) {
				CaisseDuJourDTO caisseDuJour = BizFactory.INSTANCE
						.createEmptyCaisseDuJourDTO();

				caisseDuJour.setId(rs.getInt("id_caisse_du_jour"));
				caisseDuJour.setUtilisateur(UccViewer.INSTANCE
						.leCompteUtilisateurDe(rs.getString("id_utilisateur")));
				Calendar ouverture = Calendar.getInstance();
				ouverture.setTimeInMillis(rs.getTimestamp("ouverture")
						.getTime());
				caisseDuJour.setOuverture(ouverture);
				caisseDuJour.setFondDeCaisseDeDepart(rs
						.getDouble("fond_de_caisse_depart"));
				Calendar fermeture = Calendar.getInstance();
				if (rs.getTimestamp("fermeture") == null)
					fermeture = null;
				else
					fermeture.setTimeInMillis(rs.getTimestamp("fermeture")
							.getTime());
				caisseDuJour.setFermeture(fermeture);
				caisseDuJour.setFondDeCaisseDeFermeture(rs
						.getDouble("fond_de_caisse_fermeture"));
				caisseDuJour.setRemunerationUtilisateur(rs
						.getDouble("remuneration_utilisateur"));
				caisseDuJour.setOperations(UccViewer.INSTANCE
						.lesOperationsDeLaCaisse(caisseDuJour));

				listeCaissesDuJour.add(caisseDuJour);
			}
			return listeCaissesDuJour;
		} catch (SQLException e) {
			System.out.println("[E][SQL] : ");
			e.printStackTrace();
		}
		return null;
	}

	public ArrayList<CaisseDuJourDTO> lesCaissesDuJourCompletesPeriode(
			Calendar debut, Calendar fin) {
		ResultSet rs = null;
		ArrayList<CaisseDuJourDTO> listeCaissesDuJour = new ArrayList<CaisseDuJourDTO>();
		try {
			Timestamp time1 = new Timestamp(debut.getTimeInMillis());
			Timestamp time2 = new Timestamp(fin.getTimeInMillis());
			q3.setTimestamp(1, time1);
			q3.setTimestamp(2, time2);
			rs = q3.executeQuery();
			while (rs.next()) {
				CaisseDuJourDTO caisseDuJour = BizFactory.INSTANCE
						.createEmptyCaisseDuJourDTO();

				caisseDuJour.setId(rs.getInt("id_caisse_du_jour"));
				caisseDuJour.setUtilisateur(UccViewer.INSTANCE
						.leCompteUtilisateurDe(rs.getString("id_utilisateur")));
				Calendar ouverture = Calendar.getInstance();
				ouverture.setTimeInMillis(rs.getTimestamp("ouverture")
						.getTime());
				caisseDuJour.setOuverture(ouverture);
				caisseDuJour.setFondDeCaisseDeDepart(rs
						.getDouble("fond_de_caisse_depart"));
				Calendar fermeture = Calendar.getInstance();
				if (rs.getTimestamp("fermeture") == null)
					fermeture = null;
				else
					fermeture.setTimeInMillis(rs.getTimestamp("fermeture")
							.getTime());
				caisseDuJour.setFermeture(fermeture);
				caisseDuJour.setFondDeCaisseDeFermeture(rs
						.getDouble("fond_de_caisse_fermeture"));
				caisseDuJour.setRemunerationUtilisateur(rs
						.getDouble("remuneration_utilisateur"));
				caisseDuJour.setOperations(UccViewer.INSTANCE
						.lesOperationsDeLaCaisse(caisseDuJour));

				listeCaissesDuJour.add(caisseDuJour);
			}
			return listeCaissesDuJour;
		} catch (SQLException e) {
			System.out.println("[E][SQL] : ");
			e.printStackTrace();
		}
		return null;
	}

	public CaisseDuJourDTO laCaisseOuvertePour(CompteUtilisateurDTO utilisateur) {
		ResultSet rs = null;
		try {
			q4.setString(1, utilisateur.getNomDUtilisateur());
			rs = q4.executeQuery();
			while (rs.next()) {
				CaisseDuJourDTO caisseDuJour = BizFactory.INSTANCE
						.createEmptyCaisseDuJourDTO();

				caisseDuJour.setId(rs.getInt("id_caisse_du_jour"));
				caisseDuJour.setUtilisateur(utilisateur);
				Calendar ouverture = Calendar.getInstance();
				ouverture.setTimeInMillis(rs.getTimestamp("ouverture")
						.getTime());
				caisseDuJour.setOuverture(ouverture);
				caisseDuJour.setFondDeCaisseDeDepart(rs
						.getDouble("fond_de_caisse_depart"));
				Calendar fermeture = Calendar.getInstance();
				if (rs.getTimestamp("fermeture") == null)
					fermeture = null;
				else
					fermeture.setTimeInMillis(rs.getTimestamp("fermeture")
							.getTime());
				caisseDuJour.setFermeture(fermeture);
				caisseDuJour.setFondDeCaisseDeFermeture(rs
						.getDouble("fond_de_caisse_fermeture"));
				caisseDuJour.setRemunerationUtilisateur(rs
						.getDouble("remuneration_utilisateur"));
				caisseDuJour.setOperations(UccViewer.INSTANCE
						.lesOperationsDeLaCaisse(caisseDuJour));

				return caisseDuJour;
			}
			return null;
		} catch (SQLException e) {
			System.out.println("[E][SQL] : ");
			e.printStackTrace();
		}
		return null;
	}

	public double leFondDeCaisseLogique(CaisseDuJourDTO caisseDuJour) {
		ResultSet rs = null;
		try {
			q5.setInt(1, caisseDuJour.getId());
			rs = q5.executeQuery();
			while (rs.next()) {
				return rs.getDouble("montant");
			}
			return 0;
		} catch (SQLException e) {
			System.out.println("[E][SQL] : ");
			e.printStackTrace();
		}
		return 0;
	}

	@Override
	public ArrayList<ProduitDTO> lesProduitsVendusTrie(
			CaisseDuJourDTO caisseDuJour, ClasseDeProduitDTO classe,
			boolean venteAnimateur) {
		ResultSet rs = null;
		ArrayList<ProduitDTO> listeProduits = new ArrayList<ProduitDTO>();
		try {
			q6.setInt(1, caisseDuJour.getId());
			q6.setInt(2, classe.getId());
			q6.setBoolean(3, venteAnimateur);
			rs = q6.executeQuery();
			while (rs.next()) {
				listeProduits.add(UccViewer.INSTANCE.leProduitNum(rs
						.getInt("id_produit")));
			}
			return listeProduits;
		} catch (SQLException e) {
			System.out.println("[E][SQL] : ");
			e.printStackTrace();
		}
		return null;
	}
}
